﻿namespace AsyncAwait01
{
    internal class Program
    {
        static async Task Main(string[] args)
        {
            #region 多线程实战编程4.7
            var cts = new CancellationTokenSource();
            var longTask = new Task<int>(() => TaskMethod("Task 1", 10, cts.Token), cts.Token);

            Console.WriteLine(longTask.Status);
            cts.Cancel();
            Console.WriteLine(longTask.Status);
            Console.WriteLine("First task has been cancelled before execution");

            longTask.Start();


            cts = new CancellationTokenSource();
            longTask = new Task<int>(() => TaskMethod("Task 2", 10, cts.Token), cts.Token);
            longTask.Start();
            for (int i = 0; i < 5; i++)
            {
                Thread.Sleep(TimeSpan.FromSeconds(0.5));
                Console.WriteLine(longTask.Status);
            }
            cts.Cancel();
            for (int i = 0; i < 5; i++)
            {
                Thread.Sleep(TimeSpan.FromSeconds(0.5));
                Console.WriteLine(longTask.Status);
            }
            Console.WriteLine($"A task has been completed with result {longTask.Result}"); 
            #endregion

















            //#region Task的取消
            //try
            //{
            //    var cts = new CancellationTokenSource(TimeSpan.FromSeconds(3));

            //    await Task.Delay(TimeSpan.FromSeconds(5), cts.Token);
            //}
            //catch (TaskCanceledException ex)
            //{
            //    Console.WriteLine(ex.ToString());
            //    throw;
            //}
            //catch (Exception)
            //{

            //    throw;
            //}
            //#endregion

            //Task t = AsynchronyWithTPL();
            //t.Wait();

            //t = AsynchronyWithAwait();
            //t.Wait();
            Console.ReadKey();
        }

        #region 多线程实战编程5.2
        static Task AsynchronyWithTPL()
        {
            Task<string> t = GetInfoAsync("Task 1");

            Task t2 = t.ContinueWith(task =>
                Console.WriteLine(task.Result), TaskContinuationOptions.NotOnFaulted);

            Task t3 = t.ContinueWith(task =>
                Console.WriteLine(t.Exception.InnerException), TaskContinuationOptions.OnlyOnFaulted);

            return Task.WhenAny(t2, t3);

        }
        static async Task AsynchronyWithAwait()
        {
            try
            {
                string result = await GetInfoAsync("Task 2");
                Console.WriteLine(result);
            }
            catch (Exception ex)
            {
                Console.WriteLine(ex);
            }

        }
        static async Task<string> GetInfoAsync(string name)
        {
            await Task.Delay(TimeSpan.FromSeconds(2));
            return $"Task {name} is running on a thread id {Thread.CurrentThread.ManagedThreadId} IS " +
                $"thread pool thread:{Thread.CurrentThread.IsThreadPoolThread}";
        }
        #endregion


        #region 多线程实战编程4.7
        static int TaskMethod(string name, int seconds, CancellationToken token)
        {
            Console.WriteLine($"Task {name} is running on a thread id {Thread.CurrentThread.ManagedThreadId} IS thread pool thread:{Thread.CurrentThread.IsThreadPoolThread}");
            for (int i = 0; i < seconds; i++)
            {
                Thread.Sleep(TimeSpan.FromSeconds(1));
                if (token.IsCancellationRequested)
                {
                    return -1;
                }
            }
            return 42 * seconds;
        }
        #endregion
    }
}
